package org.mobilesynergies.tuneserver;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.Iterator;

import iTunes.def.IITPlaylist;
import iTunes.def.IITPlaylistCollection;
import iTunes.def.IITSource;
import iTunes.def.IITSourceCollection;
import iTunes.def.IITTrack;
import iTunes.def.IITTrackCollection;
import iTunes.def.IiTunes;

import org.mobilesynergies.epic.client.remoteui.EpicCommand;
import org.mobilesynergies.epic.client.remoteui.IntParameter;
import org.mobilesynergies.epic.client.remoteui.OptionParameter;
import org.mobilesynergies.epic.client.remoteui.Parameter;
import org.mobilesynergies.epic.client.remoteui.ParameterMap;
import org.mobilesynergies.epic.client.remoteui.StringParameter;

public class ChooseTrackCommand extends EpicCommand{


	private TuneStarter mApplication = null;
	private String mUserSelectedPlaylist;
	
	//private String mSelectedPlaylist = "";
	//private String mSelectedTrack = "";


	public ChooseTrackCommand( ) {
		mApplication = TuneStarter.getApplicationInstance();		
	}


	@Override
	public String getHumanReadableName() {
		return "Choose a track";
	}

	@Override
	public String getId() {
		return "iTunesChooseTrack";
	}

	@Override
	public boolean hasPermission(String jid) {
		return true;
	}

	@Override
	public void cancel() {
	}

	@Override
	public void finalize(ParameterMap response) {
	}

	@Override
	public ParameterMap initialize() {
		return initCommand();
	}

	@Override
	public boolean isLastStage() {
		return false;
	}

	@Override
	public ParameterMap nextStage(ParameterMap response) {
		return updateParameters(response);
	}


	private ParameterMap initCommand() {

		IiTunes iTunes = mApplication.getITunesController();
		
		IITPlaylist nowPlayingPlaylist = iTunes.currentPlaylist();
		IITTrack nowPlayingTrack = iTunes.currentTrack();

		ParameterMap map = new ParameterMap();

		if(nowPlayingTrack==null) {
			map.putString("Now Playing", "nothing...");
			map.setLabel("Now Playing", "Now Playing");
		} else {
			map.putString("Now Playing", nowPlayingTrack.name() + " (" + nowPlayingTrack.artist() + ")");
			map.setLabel("Now Playing", "Now Playing");
		}

		IntParameter intparam = new IntParameter((int)iTunes.soundVolume(), 0, 100);
		map.putParameter("Volume", intparam);
		map.setLabel("Volume", "Volume");
		map.setSubmitActionHint("Volume", true);

		IITSource source = iTunes.librarySource();
		IITPlaylistCollection playlists = source.playlists();
		if((playlists==null) || (playlists.count()==0)){
			return map;
		}

		ArrayList<Parameter> listPlaylists = new ArrayList<Parameter>();
		for(int j=1; j<=playlists.count(); j++){
			IITPlaylist playlist = playlists.item(j);
			listPlaylists.add(new StringParameter(playlist.name()));
		}
		
		OptionParameter playlistOptions = getPlaylistsOptions();
		playlistOptions.setLabel("Playlists");
		playlistOptions.setSubmitActionHint(true);
			
		if(nowPlayingPlaylist!=null){
			playlistOptions.setValue(nowPlayingPlaylist.name());
		}
		
		map.putParameter("Playlists", playlistOptions);

		//get the track options
		OptionParameter trackOptions = null;
		if(nowPlayingPlaylist==null){
			IITPlaylist playlist = source.playlists(1);
			trackOptions = getTrackOptions(playlist.name());
		} else {
			trackOptions = getTrackOptions(nowPlayingPlaylist.name());
		}
		
		trackOptions.setLabel("Tracks");
		trackOptions.setSubmitActionHint(true);
		
		if(nowPlayingTrack!=null){
			trackOptions.setValue(nowPlayingTrack.name());
		}
		map.putParameter("Tracks", trackOptions);

		return map;
	}


	private ParameterMap updateParameters(ParameterMap updateMap) {

		if(updateMap==null){
			return initCommand();
		}

		IntParameter volumeParameter = null;
		StringParameter currentlyPlayingParameter = null;
		OptionParameter playlistOptions = null;
		OptionParameter trackOptions = null;
		
		
		
		IiTunes iTunes = mApplication.getITunesController();
		
		if(updateMap.containsKey("Volume")){
			//update volume
			int iCurrentVolume = iTunes.soundVolume();
			if(iTunes != null){
				iTunes.soundVolume(updateMap.getInt("Volume", iCurrentVolume));
			}
			
			volumeParameter = new IntParameter((int)iTunes.soundVolume(), 0, 100);
			volumeParameter.setLabel("Volume");
			volumeParameter.setSubmitActionHint(true);
		}
		
		boolean bStartTrack = true;
		if(updateMap.containsKey("Playlists")){
			//update playlist and tracks
			String newUserSelectedPlaylist = updateMap.getOptionValue("Playlists", "");
			if(newUserSelectedPlaylist.equalsIgnoreCase(mUserSelectedPlaylist)){
				//no need to update the playlist value
				//maybe a new track shall be started
				bStartTrack = true;				
			} else {
				//updating the trackslist
				mUserSelectedPlaylist=newUserSelectedPlaylist;
				bStartTrack = false;
				playlistOptions = getPlaylistsOptions();
				playlistOptions.setValue(mUserSelectedPlaylist);
				trackOptions = getTrackOptions(mUserSelectedPlaylist);
				
			}
		}
		
		if(bStartTrack){
			
			if(updateMap.containsKey("Tracks")){
				//start playing new track
				String userSelectedTrack = updateMap.getOptionValue("Tracks", "");
				String playlist = "";
				if((mUserSelectedPlaylist==null)||(mUserSelectedPlaylist.length()==0)) {
					//try default playlist 
					playlist = iTunes.libraryPlaylist().name();
				} else {
					playlist = mUserSelectedPlaylist;
				}
				playTrack(playlist, userSelectedTrack);
				trackOptions = getTrackOptions(mUserSelectedPlaylist);
				trackOptions.setValue(userSelectedTrack);				
			}
		}
		
		IITTrack track = iTunes.currentTrack();
		
		if(track==null) {
			currentlyPlayingParameter = new StringParameter("nothing...");
			currentlyPlayingParameter.setLabel("Now Playing");
		} else {
			currentlyPlayingParameter = new StringParameter(track.name() + " (" + track.artist() + ")");
			currentlyPlayingParameter.setLabel("Now Playing");
			//	System.out.println("Now playing album: "+ track.album() + ", track name: "+track.name()+", by: "+track.artist()+", duration: "+track.duration());
		}		

		ParameterMap outputMap = new ParameterMap();
		if(currentlyPlayingParameter!=null){
			outputMap.putParameter("Now Playing", currentlyPlayingParameter);
		}
		
		if(volumeParameter!=null){
			outputMap.putParameter("Volume", volumeParameter);
		}
		
		if(playlistOptions!=null){
			outputMap.putParameter("Playlists", playlistOptions);
		}
		
		if(trackOptions!=null){
			outputMap.putParameter("Tracks", trackOptions);
		}
		
		return outputMap;

	}


	
	@Override
	public ParameterMap previousStage() {
		return initialize();		
	}

	public OptionParameter getPlaylistsOptions(){

		IiTunes iTunes = mApplication.getITunesController();
		IITSource source = iTunes.librarySource();

		IITPlaylistCollection playlists = source.playlists();

		ArrayList<Parameter> listPlaylists = new ArrayList<Parameter>();
		
		for(int j=1; j<=playlists.count(); j++){
			IITPlaylist playlist = playlists.item(j);
			listPlaylists.add(new StringParameter(playlist.name()));			
		}
		
		OptionParameter param = new OptionParameter(listPlaylists);
		param.setLabel("Playlists");
		param.setSubmitActionHint(true);
		
		return param;
	}

	public OptionParameter getTrackOptions(String playlistName){
		IiTunes iTunes = mApplication.getITunesController();
		IITSource source = iTunes.librarySource();
		
		IITPlaylistCollection playlists = source.playlists();
		IITPlaylist playlist = playlists.itemByName(playlistName);
		if(playlist == null) {
			return null;
		}
		
		IITTrackCollection tracks = playlist.tracks();
		ArrayList<Parameter> listTracks = new ArrayList<Parameter>();
		for(int k=1; k<=tracks.count(); k++){
			IITTrack track = tracks.item(k);
			listTracks.add(new StringParameter(track.name()));
		}
		OptionParameter param = new OptionParameter(listTracks);
		param.setLabel("Tracks");
		param.setSubmitActionHint(true);
		
		
		return param;
	}

	public void playTrack(String playlistName, String trackName) {
		IiTunes iTunes = mApplication.getITunesController();
		IITSource source = iTunes.librarySource();
		IITPlaylistCollection playlists = source.playlists();
		IITPlaylist playlist = playlists.itemByName(playlistName);
		if(playlist == null) {
			//TODO display error
			return;
		}
		IITTrackCollection tracks = playlist.tracks();
		IITTrack track = tracks.itemByName(trackName);
		if(track==null){
			//TODO display error
			return;
		}
		track.play();
	}





}